﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using Qu.SeniorProject.Model;
using System.IO;
using System.Threading.Tasks;
using System.Net;
using HtmlAgilityPack;

namespace Qu.SeniorProject.WebUI.Controllers
{
    public class DocumentController : Controller
    {
        private bool UrlExists(String url) {
            var request = (HttpWebRequest)WebRequest.Create(url);
            request.Method = "HEAD";

            try
            {
                var response = (HttpWebResponse)request.GetResponse();
                return (response.StatusCode == HttpStatusCode.OK);
            }
            catch (Exception ex)
            {
                return false;
            }
        }

        public async Task<JsonResult> DeliverableUrlSubmission()
        {
            bool isPreziDocument = false;
            var documentType = Request["DocumentType"];
            int projectId = int.Parse(Request["ProjectId"]);
            string documentExtension = Request["DocumentExtension"];
            int academicYear = int.Parse(Request["AcademicYear"]);
            string sourceUrl = Request["SourceUrl"];

            if (String.IsNullOrEmpty(sourceUrl))
            {
                sourceUrl = Request["PreziUrl"];
                isPreziDocument = true;

                if (String.IsNullOrEmpty(sourceUrl) || !UrlExists(sourceUrl))
                {
                    return Json(new
                    {
                        status = "failed",
                        message = "The submitted Url is invalid"
                    }, JsonRequestBehavior.AllowGet);
                }
            }

            var documentPath = String.Empty;
            var documentName = String.Empty;
            var documentUrl = String.Empty;

            if (!isPreziDocument)
            {
                documentPath = Path.Combine(this.Server.MapPath("~/uploads/"), academicYear.ToString());

                if (!System.IO.Directory.Exists(documentPath))
                    System.IO.Directory.CreateDirectory(documentPath);

                documentPath = Path.Combine(documentPath, documentType);

                if (!System.IO.Directory.Exists(documentPath))
                    System.IO.Directory.CreateDirectory(documentPath);

                documentName = string.Format("Project{0}-{1}{2}", projectId, documentType, documentExtension);
                documentPath = Path.Combine(documentPath, documentName);

                documentUrl = HttpUtility.HtmlEncode(string.Format("{0}{1}/{2}/{3}", "uploads/",
                    academicYear,
                    documentType, documentName));
            }

            var userInfo = Session["UserInfo"] as UserInfo;

            var documentSubmission = new DocumentSubmission
            {
                ProjectId = projectId,
                DocumentType = documentType,
                AcademicYear = academicYear,
                DocumentExtension = documentExtension,
                SourceUrl = sourceUrl,
                DocumentName = documentName,
                DocumentUrl = documentUrl,
                DocumentPhysicalPath = documentPath,
                SubmittedBy = userInfo.LoginName
            };


            if (isPreziDocument)
            {
                ProjectRepository.AddProjectDocument(documentSubmission);
                return Json(new
                {
                    status = "ok",
                    message = "The submitted Prezi link was successfully received.",
                    documentName = documentName,
                    sourceUrl = sourceUrl
                }, JsonRequestBehavior.AllowGet);
            }

            WebClient webClient = new WebClient();
            string souceHtml = webClient.DownloadString(sourceUrl);

            HtmlDocument document = new HtmlDocument();
            document.LoadHtml(souceHtml);
            HtmlNode downloadLinkNode = document.DocumentNode.SelectSingleNode("//*[@id='default_content_download_button']");

            HtmlAttribute att = downloadLinkNode.Attributes["href"];
            sourceUrl = att.Value;



            await Task.Run(() => DownloadFile(documentSubmission));

            // Return json object for fire and forget.
            return Json(new 
                    {
                       status = "ok",
                       message = "The submitted document link was successfully received and it will be processed shortly. A confirmation email will be sent to you.",
                       documentName = documentName,
                       sourceUrl = sourceUrl
                    }, JsonRequestBehavior.AllowGet);
        }

        private void DownloadFile(DocumentSubmission documentSubmission)
        {

            WebClient webClient = new WebClient();
            webClient.DownloadProgressChanged += (s, e) =>
            {
                System.Diagnostics.Trace.WriteLine(string.Format("Download Progress % {0}", e.ProgressPercentage));
            };
            webClient.DownloadFileCompleted += (s, e) =>
            {
                System.Diagnostics.Trace.WriteLine("Download done - ToDo Save Document Info to DB");
                ProjectRepository.AddProjectDocument(documentSubmission);
            };

            webClient.DownloadFileAsync(new Uri(documentSubmission.SourceUrl), documentSubmission.DocumentPhysicalPath);

        }

        //get link with id="default_content_download_button"


        [HttpPost]
        public ActionResult Upload(HttpPostedFileBase file) //(string qqfile)
        {
            var docType = Request["DocumentType"];
            int projectId = int.Parse(Request["ProjectId"]);
            string docExtension = Request["DocumentExtension"];
            string academicYear = Request["AcademicYear"];

            var destinationFolder = Path.Combine(this.Server.MapPath("~/uploads/"), academicYear); //DateTime.Now.Year.ToString());

            if (!System.IO.Directory.Exists(destinationFolder))
                System.IO.Directory.CreateDirectory(destinationFolder);

            destinationFolder = Path.Combine(destinationFolder, docType);

            if (!System.IO.Directory.Exists(destinationFolder))
                System.IO.Directory.CreateDirectory(destinationFolder);

            var fileName = string.Format("Project{0}-{1}{2}", projectId, docType, docExtension);
            var filePath = Path.Combine(destinationFolder, fileName);

            var docUrl = HttpUtility.HtmlEncode(string.Format("{0}{1}/{2}/{3}", "uploads/", academicYear, docType, fileName));

            try
            {
                //HttpPostedFileBase hpf = Request.Files[0] as HttpPostedFileBase;
                file.SaveAs(filePath);

                //var stream = Request.InputStream;
                ////if (String.IsNullOrEmpty(Request["qqfile"]))
                ////{
                ////    // IE
                ////    HttpPostedFileBase postedFile = Request.Files[0];
                ////    stream = postedFile.InputStream;
                ////    file = Path.Combine(path, System.IO.Path.GetFileName(Request.Files[0].FileName));
                ////}
                ////else
                ////{
                ////    //Webkit, Mozilla
                ////    file = Path.Combine(path, qqfile);
                ////}

                //var buffer = new byte[stream.Length];
                //stream.Read(buffer, 0, buffer.Length);
                //System.IO.File.WriteAllBytes(filePath, buffer);
                //stream.Flush();
                //stream.Close();

                var userInfo = Session["UserInfo"] as UserInfo;
                var documentSubmission = new DocumentSubmission
                {
                    ProjectId = projectId,
                    DocumentType = docType,
                    DocumentExtension = docExtension,
                    DocumentUrl = docUrl,
                    DocumentName = fileName,
                    SourceUrl = String.Empty,
                    SubmittedBy = userInfo.LoginName
                };

                ProjectRepository.AddProjectDocument(documentSubmission);
                TempData["Message"] = string.Format("File '{0}' uploaded successfully", file.FileName);
            }
            catch (Exception ex)
            {
                TempData["Message"] = string.Format("File '{0}' upload failed {1}", file.FileName, ex.Message);
                return RedirectToAction("Index", "Home");
            }
            return RedirectToAction("Index", "Home");

            //catch (Exception ex)
            //{
            //    return Json(new { success = false, message = ex.Message }, "text/html");
            //}

            //return Json(new { success = true, message = string.Format("<a href='{0}'>{1}</a>", docUrl, fileName) }, "text/html");

            //var destinationFolder = string.Format("{0}{1}", this.Server.MapPath("~/uploads/"), DateTime.Now.Year);

            //if (!System.IO.Directory.Exists(destinationFolder))
            //    System.IO.Directory.CreateDirectory(destinationFolder);

            //var fileName = string.Format("Project{0}-{1}{2}", Request["ProjectId"], Request["DocumentType"], Request["DocumentExtension"]);
            //var filePath = string.Format(@"{0}\{1}", destinationFolder, fileName);
            //fileData.SaveAs(filePath);

            //var url = HttpUtility.HtmlEncode(string.Format("{0}{1}/{2}", "uploads/", DateTime.Now.Year, fileName));
            //return string.Format("<a href='{0}'>{1}<a>", url, fileName);

        }

        private UserInfo GetUserInfo()
        {
            var userInfo = Session["UserInfo"] as UserInfo;
            if (Request.IsAuthenticated && userInfo == null)
            {
                //Store the User Info in a Session
                userInfo = UserRepository.GetUserInfo(User.Identity.Name);

                if (userInfo != null)
                    Session["UserInfo"] = userInfo;
            }
            return userInfo;
        }

        public ActionResult Index(string id)
        {
            var userInfo = GetUserInfo();

            if (userInfo == null)
                return RedirectToAction("LogOn", "Account");

            if (!string.IsNullOrEmpty(id))
            {
                if (id.StartsWith("pd"))
                {
                    id = id.Remove(0, 2);
                    //Request Template and Guides
                    var docInfo = DocumentRepository.GetProjectDocument(int.Parse(id));
                    var filePath = string.Empty;

                    if (docInfo != null)
                        return File(Path.Combine(Server.MapPath("~/"), docInfo.DocumentPath), string.Format("application/{0}", docInfo.DocumentExtension), docInfo.DocumentName);
                    else
                        return RedirectToAction("Index", "Home");
                }
                else
                {
                    //Request Template and Guides
                    var docInfo = DocumentRepository.Get(int.Parse(id));
                    var filePath = string.Empty;

                    if (docInfo != null)
                        return File(Path.Combine(Server.MapPath("~/App_Data"), docInfo.Path, docInfo.FileName), string.Format("application/{0}", docInfo.Extension), docInfo.FileName);
                }
            }

            ViewBag.Major = userInfo.Major;

            var documents = DocumentRepository.GetAll();
            return View(documents);
        }

    }
}
